#!/bin/sh

e2e_test_install() {
  NODE_LABEL_KEY="$(random_string)"
  NODE_LABEL_VALUE="$(random_string)"

  DEFAULT_PGCONFIG="defaultpgconfig"
  PGCBOUNCER="pgbouncer"
  PGCONFIG="postgresconf"
  BACKUP_CONFIG="backupconf"
  INSTANCE_PROFILE="size-x"
  DISTRIBUTEDLOGS_NAME="$(get_sgdistributedlogs_name distributedlogs)"
  PGBOUNCER_CLUSTER_NAME="$(get_sgcluster_name "$CLUSTER_NAME-pgbouncer")"
  REUSED_CLUSTER_NAME="$(get_sgcluster_name "$CLUSTER_NAME-reused")"
  NOSIDECARS_CLUSTER_NAME="$(get_sgcluster_name "$CLUSTER_NAME-nosidecars")"

  kubectl create namespace "$CLUSTER_NAMESPACE"
  deploy_curl_pod "$CLUSTER_NAMESPACE"
  wait_pods_running "$CLUSTER_NAMESPACE" 1
}

e2e_test_uninstall() {
  k8s_async_cleanup_namespace "$CLUSTER_NAMESPACE"
}

e2e_test() {
  run_test "Creating an empty sgpgconfig should be filled with default configurations" create_empty_sgpgconfig

  run_test "Updating an empty sgpgconfig should be filled with default configurations" update_empty_sgpgconfig

  run_test "Creating an empty sgpoolconfig should be filled with default configurations" create_empty_sgpoolconfig

  run_test "Updating an empty sgpoolconfig should be filled with default configurations" update_empty_sgpoolconfig

  run_test "Creating an empty sgobjectstorage should be filled with default configurations" create_empty_sgobjectstorage

  run_test "Updating an empty sgobjectstorage should be filled with default configurations" update_empty_sgobjectstorage

  run_test "Creating an sginstanceprofile should be filled with default configurations" create_sginstanceprofile

  run_test "Updating an sginstanceprofile should be filled with default configurations" update_sginstanceprofile

  run_test "If default configuration are already created it should create the cluster" create_empty_cluster_with_default_pgbouncer

  run_test "If the sidecars are specifically set to be empty the operator should not add any sidecar" create_empty_cluster_with_no_sidecars

  run_test "Creating an empty cluster should trigger the creation of all default configurations" create_empty_cluster

  run_test "Updating a cluster without annotations should trigger the creation of annotations" update_empty_cluster

  run_test "Creating an empty cluster with previous postgres version should not fail" create_cluster_with_previous_postgres_version

  run_test "Creating an empty distributed logs should trigger the creation of all default configurations" create_empty_distributedlogs

  run_test "Updating a distributed logs without annotations should trigger the creation of annotations" update_empty_distributedlogs

  run_test "Creating an empty sharded cluster should trigger the creation of all default configurations" create_empty_sharded_cluster

  run_test "Updating a sharded cluster without annotations should trigger the creation of annotations" update_empty_sharded_cluster

  run_test "Creating an empty sharded cluster with previous postgres version should not fail" create_sharded_cluster_with_previous_postgres_version
}

create_empty_sgpgconfig() {
  kubectl delete sgpgconfig -n "$CLUSTER_NAMESPACE" "$PGCONFIG" --ignore-not-found
  cat << EOF > "$LOG_PATH/create-empty-sgpgconfig.yaml"
apiVersion: stackgres.io/v1
kind: SGPostgresConfig
metadata:
  name: $PGCONFIG
  namespace: $CLUSTER_NAMESPACE
spec:
  postgresVersion: "${E2E_POSTGRES_VERSION%%.*}"
  postgresql.conf:
    custom.unsignificant: "true"
EOF

  kubectl create -f "$LOG_PATH/create-empty-sgpgconfig.yaml"

  local CREATED_FIELDS
  CREATED_FIELDS="$(kubectl get sgpgconfigs.stackgres.io -n "$CLUSTER_NAMESPACE" "$PGCONFIG" -o json | jq '.spec["postgresql.conf"] | length')"

  if [ "$CREATED_FIELDS" -gt 1 ]
  then
    success "Defaults fields filled"
  else
    fail "Default fields not filled"
  fi

  local CREATED_DEFAULTS_PARAMETERS
  CREATED_DEFAULTS_PARAMETERS="$(kubectl get sgpgconfigs.stackgres.io -n "$CLUSTER_NAMESPACE" "$PGCONFIG" -o json | jq '.status.defaultParameters | length')"

  if [ "$CREATED_DEFAULTS_PARAMETERS" -gt 0 ]
  then
    success "Defaults parameters filled"
  else
    fail "Default parameters not filled"
  fi

  local DEFAULT_ANNOTATION
  DEFAULT_ANNOTATION="$(kubectl get sgpgconfigs.stackgres.io -n "$CLUSTER_NAMESPACE" "$PGCONFIG" -o json | jq '.metadata.annotations["stackgres.io/operatorVersion"]')"

  if [ -z "$DEFAULT_ANNOTATION" ] || [ "$DEFAULT_ANNOTATION" = "null" ]
  then
    fail "Default annotations not filled"
  else
    success "Defaults annotations filled"
  fi
}

update_empty_sgpgconfig() {
  kubectl delete sgpgconfig -n "$CLUSTER_NAMESPACE" "$PGCONFIG" --ignore-not-found
  cat << EOF > "$LOG_PATH/update-empty-sgpgconfig.yaml"
apiVersion: stackgres.io/v1
kind: SGPostgresConfig
metadata:
  name: $PGCONFIG
  namespace: $CLUSTER_NAMESPACE
spec:
  postgresVersion: "${E2E_POSTGRES_VERSION%%.*}"
  postgresql.conf: {}
EOF

  kubectl create -f "$LOG_PATH/update-empty-sgpgconfig.yaml"

  kubectl get sgpgconfig -n "$CLUSTER_NAMESPACE" "$PGCONFIG" -o json \
    | jq 'del(.metadata.resourceVersion)|del(.metadata.uid)|del(.metadata.creationTimestamp)|del(.metadata.selfLink)|del(.metadata.geneartion)' \
    | jq 'del(.metadata.annotations["stackgres.io/operatorVersion"])|.spec["postgresql.conf"]["custom.unsignificant"] = "true"' \
    | kubectl create -f - --dry-run=client -o yaml > "$LOG_PATH/patch-empty-sgpgconfig.yaml"
  kubectl patch sgpgconfig -n "$CLUSTER_NAMESPACE" "$PGCONFIG" --type merge --patch-file="$LOG_PATH/patch-empty-sgpgconfig.yaml"

  local UPDATED_FIELDS
  UPDATED_FIELDS="$(kubectl get sgpgconfigs.stackgres.io -n "$CLUSTER_NAMESPACE" "$PGCONFIG" -o json | jq '.spec["postgresql.conf"] | length')"

  if [ "$UPDATED_FIELDS" -gt 0 ]
  then
    success "Defaults fields filled"
  else
    fail "Default fields not filled"
  fi

  local UPDATED_DEFAULTS_PARAMETERS
  UPDATED_DEFAULTS_PARAMETERS="$(kubectl get sgpgconfigs.stackgres.io -n "$CLUSTER_NAMESPACE" "$PGCONFIG" -o json | jq '.status.defaultParameters | length')"

  if [ "$UPDATED_DEFAULTS_PARAMETERS" -gt 0 ]
  then
    success "Defaults parameters filled"
  else
    fail "Default parameters not filled"
  fi

  local DEFAULT_ANNOTATION
  DEFAULT_ANNOTATION="$(kubectl get sgpgconfigs.stackgres.io -n "$CLUSTER_NAMESPACE" "$PGCONFIG" -o json | jq '.metadata.annotations["stackgres.io/operatorVersion"]')"

  if [ -z "$DEFAULT_ANNOTATION" ] || [ "$DEFAULT_ANNOTATION" = "null" ]
  then
    fail "Default annotations not filled"
  else
    success "Defaults annotations filled"
  fi
}

create_empty_sgpoolconfig() {
  kubectl delete sgpoolconfig -n "$CLUSTER_NAMESPACE" "$PGCBOUNCER" --ignore-not-found
  cat << EOF > "$LOG_PATH/create-empty-sgpoolconfig.yaml"
apiVersion: stackgres.io/v1
kind: SGPoolingConfig
metadata:
  name: $PGCBOUNCER
  namespace: $CLUSTER_NAMESPACE
spec:
  pgBouncer:
    pgbouncer.ini:
      pgbouncer:
        unsignificant: "true"
EOF

  kubectl create -f "$LOG_PATH/create-empty-sgpoolconfig.yaml"

  local CREATED_FIELDS
  CREATED_FIELDS="$(kubectl get sgpoolconfigs.stackgres.io -n "$CLUSTER_NAMESPACE" "$PGCBOUNCER" -o json | jq '.spec.pgBouncer["pgbouncer.ini"].pgbouncer | length')"

  if [ "$CREATED_FIELDS" -gt 1 ]
  then
    success "Defaults fields filled"
  else
    fail "Default fields not filled"
  fi

  local CREATED_DEFAULTS_PARAMETERS
  CREATED_DEFAULTS_PARAMETERS="$(kubectl get sgpoolconfigs.stackgres.io -n "$CLUSTER_NAMESPACE" "$PGCBOUNCER" -o json | jq '.status.pgBouncer.defaultParameters | length')"

  if [ "$CREATED_DEFAULTS_PARAMETERS" -gt 0 ]
  then
    success "Defaults parameters filled"
  else
    fail "Default parameters not filled"
  fi

  local DEFAULT_ANNOTATION
  DEFAULT_ANNOTATION="$(kubectl get sgpoolconfigs.stackgres.io -n "$CLUSTER_NAMESPACE" "$PGCBOUNCER" -o json | jq '.metadata.annotations["stackgres.io/operatorVersion"]')"

  if [ -z "$DEFAULT_ANNOTATION" ] || [ "$DEFAULT_ANNOTATION" = "null" ]
  then
    fail "Default annotations not filled"
  else
    success "Defaults annotations filled"
  fi
}

update_empty_sgpoolconfig() {
  kubectl delete sgpoolconfig -n "$CLUSTER_NAMESPACE" "$PGCBOUNCER" --ignore-not-found
  cat << EOF > "$LOG_PATH/update-empty-sgpoolconfig.yaml"
apiVersion: stackgres.io/v1
kind: SGPoolingConfig
metadata:
  name: $PGCBOUNCER
  namespace: $CLUSTER_NAMESPACE
spec: {}
EOF

  kubectl create -f "$LOG_PATH/update-empty-sgpoolconfig.yaml"

  kubectl get sgpoolconfig -n "$CLUSTER_NAMESPACE" "$PGCBOUNCER" -o json \
    | jq 'del(.metadata.resourceVersion)|del(.metadata.uid)|del(.metadata.creationTimestamp)|del(.metadata.selfLink)|del(.metadata.geneartion)' \
    | jq 'del(.metadata.annotations["stackgres.io/operatorVersion"])|.spec.pgBouncer["pgbouncer.ini"].pgbouncer.unsignificant = "true"' \
    | kubectl create -f - --dry-run=client -o yaml > "$LOG_PATH/patch-empty-sgpoolconfig.yaml"
  kubectl patch sgpoolconfig -n "$CLUSTER_NAMESPACE" "$PGCBOUNCER" --type merge --patch-file="$LOG_PATH/patch-empty-sgpoolconfig.yaml"

  local UPDATED_FIELDS
  UPDATED_FIELDS="$(kubectl get sgpoolconfigs.stackgres.io -n "$CLUSTER_NAMESPACE" "$PGCBOUNCER" -o json | jq '.spec.pgBouncer["pgbouncer.ini"].pgbouncer | length')"

  if [ "$UPDATED_FIELDS" -gt 0 ]
  then
    success "Defaults fields filled"
  else
    fail "Default fields not filled"
  fi

  local UPDATED_DEFAULTS_PARAMETERS
  UPDATED_DEFAULTS_PARAMETERS="$(kubectl get sgpoolconfigs.stackgres.io -n "$CLUSTER_NAMESPACE" "$PGCBOUNCER" -o json | jq '.status.pgBouncer.defaultParameters | length')"

  if [ "$UPDATED_DEFAULTS_PARAMETERS" -gt 0 ]
  then
    success "Defaults parameters filled"
  else
    fail "Default parameters not filled"
  fi

  local DEFAULT_ANNOTATION
  DEFAULT_ANNOTATION="$(kubectl get sgpoolconfigs.stackgres.io -n "$CLUSTER_NAMESPACE" "$PGCBOUNCER" -o json | jq '.metadata.annotations["stackgres.io/operatorVersion"]')"

  if [ -z "$DEFAULT_ANNOTATION" ] || [ "$DEFAULT_ANNOTATION" = "null" ]
  then
    fail "Default annotations not filled"
  else
    success "Defaults annotations filled"
  fi
}

create_empty_sgobjectstorage() {
  kubectl create secret generic -n "$CLUSTER_NAMESPACE" "minio" \
     --from-literal=accesskey=test --from-literal=secretkey=test
     
  kubectl delete sgobjectstorages.stackgres.io -n "$CLUSTER_NAMESPACE" "$BACKUP_CONFIG" --ignore-not-found
  cat << EOF > "$LOG_PATH/create-empty-sgobjectstorage.yaml"
apiVersion: stackgres.io/v1beta1
kind: SGObjectStorage
metadata:
  name: $BACKUP_CONFIG
  namespace: $CLUSTER_NAMESPACE
spec:
  type: s3Compatible
  s3Compatible:
    bucket: stackgres
    awsCredentials:
      secretKeySelectors:
        accessKeyId:
          name: minio
          key: accesskey
        secretAccessKey:
          name: minio
          key: secretkey
EOF

  kubectl create -f "$LOG_PATH/create-empty-sgobjectstorage.yaml"

  kubectl get sgobjectstorages.stackgres.io -n "$CLUSTER_NAMESPACE" "$BACKUP_CONFIG" -o json | jq '.spec' > "$LOG_PATH/created-fields-empty-sgobjectstorage.yaml"

  if ! grep -q . "$LOG_PATH/created-fields-empty-sgobjectstorage.yaml" \
    || grep -qxF null "$LOG_PATH/created-fields-empty-sgobjectstorage.yaml"
  then
    fail "Spec fields not filled"
  else
    success "Spec fields filled"
  fi
  
  local DEFAULT_ANNOTATION
  DEFAULT_ANNOTATION="$(kubectl get sgobjectstorages.stackgres.io -n "$CLUSTER_NAMESPACE" "$BACKUP_CONFIG" -o json | jq '.metadata.annotations["stackgres.io/operatorVersion"]')"

  if [ -z "$DEFAULT_ANNOTATION" ] || [ "$DEFAULT_ANNOTATION" = "null" ]
  then
    fail "Default annotations not filled"
  else
    success "Defaults annotations filled"
  fi
}

update_empty_sgobjectstorage() {
  kubectl delete sgobjectstorages.stackgres.io -n "$CLUSTER_NAMESPACE" "$BACKUP_CONFIG" --ignore-not-found
  cat << EOF > "$LOG_PATH/update-empty-sgobjectstorage.yaml"
apiVersion: stackgres.io/v1beta1
kind: SGObjectStorage
metadata:
  name: $BACKUP_CONFIG
  namespace: $CLUSTER_NAMESPACE
spec: {}
EOF

  kubectl create -f "$LOG_PATH/update-empty-sgobjectstorage.yaml"

  kubectl get sgobjectstorages.stackgres.io -n "$CLUSTER_NAMESPACE" "$BACKUP_CONFIG" -o json | jq '.spec' > "$LOG_PATH/previous-fields-empty-sgobjectstorage.yaml"

  kubectl get sgobjectstorages -n "$CLUSTER_NAMESPACE" "$BACKUP_CONFIG" -o json \
    | jq 'del(.metadata.resourceVersion)|del(.metadata.uid)|del(.metadata.creationTimestamp)|del(.metadata.selfLink)|del(.metadata.geneartion)' \
    | jq 'del(.metadata.annotations["stackgres.io/operatorVersion"])' \
    | kubectl create -f - --dry-run=client -o yaml > "$LOG_PATH/patch-empty-sgobjectstorage.yaml"
  kubectl patch sgobjectstorages -n "$CLUSTER_NAMESPACE" "$BACKUP_CONFIG" --type merge --patch-file="$LOG_PATH/patch-empty-sgobjectstorage.yaml"

  kubectl get sgobjectstorages.stackgres.io -n "$CLUSTER_NAMESPACE" "$BACKUP_CONFIG" -o json | jq '.spec' > "$LOG_PATH/updated-fields-empty-sgobjectstorage.yaml"

  if diff "$LOG_PATH/previous-fields-empty-sgobjectstorage.yaml" "$LOG_PATH/updated-fields-empty-sgobjectstorage.yaml"
  then
    success "Defaults fields filled"
  else
    fail "Default fields not filled"
  fi

  local DEFAULT_ANNOTATION
  DEFAULT_ANNOTATION="$(kubectl get sgobjectstorages.stackgres.io -n "$CLUSTER_NAMESPACE" "$BACKUP_CONFIG" -o json | jq '.metadata.annotations["stackgres.io/operatorVersion"]')"

  if [ -z "$DEFAULT_ANNOTATION" ] || [ "$DEFAULT_ANNOTATION" = "null" ]
  then
    fail "Default annotations not filled"
  else
    success "Defaults annotations filled"
  fi
}

create_sginstanceprofile() {
  kubectl delete sginstanceprofile -n "$CLUSTER_NAMESPACE" "$INSTANCE_PROFILE" --ignore-not-found
  cat << EOF > "$LOG_PATH/create-sginstanceprofile.yaml"
apiVersion: stackgres.io/v1
kind: SGInstanceProfile
metadata:
  name: $INSTANCE_PROFILE
  namespace: $CLUSTER_NAMESPACE
spec:
  cpu: '1'
  memory: '2Gi'
EOF

  kubectl create -f "$LOG_PATH/create-sginstanceprofile.yaml"

  kubectl get sginstanceprofiles.stackgres.io -n "$CLUSTER_NAMESPACE" "$INSTANCE_PROFILE" -o json | jq '.spec' > "$LOG_PATH/created-fields-sginstanceprofile.yaml"
  if ! grep -q . "$LOG_PATH/created-fields-sginstanceprofile.yaml" \
    || grep -qxF null "$LOG_PATH/created-fields-sginstanceprofile.yaml"
  then
    fail "Default fields not filled"
  else
    success "Defaults fields filled"
  fi

  local DEFAULT_ANNOTATION
  DEFAULT_ANNOTATION="$(kubectl get sginstanceprofiles.stackgres.io -n "$CLUSTER_NAMESPACE" "$INSTANCE_PROFILE" -o json | jq '.metadata.annotations["stackgres.io/operatorVersion"]')"

  if [ -z "$DEFAULT_ANNOTATION" ] || [ "$DEFAULT_ANNOTATION" = "null" ]
  then
    fail "Default annotations not filled"
  else
    success "Defaults annotations filled"
  fi
}

update_sginstanceprofile() {
  kubectl delete sginstanceprofile -n "$CLUSTER_NAMESPACE" "$INSTANCE_PROFILE" --ignore-not-found
  cat << EOF > "$LOG_PATH/update-sginstanceprofile.yaml"
apiVersion: stackgres.io/v1
kind: SGInstanceProfile
metadata:
  name: $INSTANCE_PROFILE
  namespace: $CLUSTER_NAMESPACE
spec:
  cpu: '1'
  memory: '2Gi'
EOF

  kubectl create -f "$LOG_PATH/update-sginstanceprofile.yaml"

  kubectl get sginstanceprofile -n "$CLUSTER_NAMESPACE" "$INSTANCE_PROFILE" -o json | jq '.spec.memory = "1Gi" | del(.spec.initContainers) | .spec' > "$LOG_PATH/previous-fields-sginstanceprofile.yaml"

  kubectl get sginstanceprofile -n "$CLUSTER_NAMESPACE" "$INSTANCE_PROFILE" -o json \
    | jq 'del(.metadata.resourceVersion)|del(.metadata.uid)|del(.metadata.creationTimestamp)|del(.metadata.selfLink)|del(.metadata.geneartion)' \
    | jq 'del(.metadata.annotations["stackgres.io/operatorVersion"])|.spec.memory = "1Gi"' \
    | kubectl create -f - --dry-run=client -o yaml > "$LOG_PATH/patch-sginstanceprofile.yaml"
  kubectl patch sginstanceprofile -n "$CLUSTER_NAMESPACE" "$INSTANCE_PROFILE" --type merge --patch-file="$LOG_PATH/patch-sginstanceprofile.yaml"

  kubectl get sginstanceprofiles.stackgres.io -n "$CLUSTER_NAMESPACE" "$INSTANCE_PROFILE" -o json | jq 'del(.spec.initContainers) | .spec' > "$LOG_PATH/updated-fields-sginstanceprofile.yaml"

  if diff "$LOG_PATH/previous-fields-sginstanceprofile.yaml" "$LOG_PATH/updated-fields-sginstanceprofile.yaml"
  then
    success "Defaults fields filled"
  else
    fail "Default fields not filled"
  fi

  local DEFAULT_ANNOTATION
  DEFAULT_ANNOTATION="$(kubectl get sginstanceprofiles.stackgres.io -n "$CLUSTER_NAMESPACE" "$INSTANCE_PROFILE" -o json | jq '.metadata.annotations["stackgres.io/operatorVersion"]')"

  if [ -z "$DEFAULT_ANNOTATION" ] || [ "$DEFAULT_ANNOTATION" = "null" ]
  then
    fail "Default annotations not filled"
  else
    success "Defaults annotations filled"
  fi
}

create_empty_cluster_with_default_pgbouncer() {
  kubectl delete sgcluster -n "$CLUSTER_NAMESPACE" "$PGBOUNCER_CLUSTER_NAME" --ignore-not-found
  cat << EOF > "$LOG_PATH/create-empty-cluster-with-default-pgbouncer.yaml"
apiVersion: stackgres.io/v1
kind: SGCluster
metadata:
  name: $PGBOUNCER_CLUSTER_NAME
  namespace: $CLUSTER_NAMESPACE
spec:
  instances: 1
  postgres:
    version: "$E2E_POSTGRES_VERSION"
  pods:
    persistentVolume:
      size: '5Gi'
    scheduling:
      nodeSelector:
        $NODE_LABEL_KEY: $NODE_LABEL_VALUE"
  nonProductionOptions:
    disableClusterPodAntiAffinity: true
EOF

  kubectl create -f "$LOG_PATH/create-empty-cluster-with-default-pgbouncer.yaml"

  local CREATED_PGBOUNCER
  CREATED_PGBOUNCER="$(kubectl get sgclusters.stackgres.io -n "$CLUSTER_NAMESPACE" "$PGBOUNCER_CLUSTER_NAME" -o='jsonpath={.spec.configurations.sgPoolingConfig}')"
  if wait_until kubectl get sgpoolconfigs.stackgres.io -n "$CLUSTER_NAMESPACE" "$CREATED_PGBOUNCER"
  then
    success "Default pgbouncer was created in the cluster namespace"
  else
    fail "Default pgbouncer was not created in the cluster namespace"
  fi

  kubectl delete sgclusters -n "$CLUSTER_NAMESPACE" "$PGBOUNCER_CLUSTER_NAME"

  cat << EOF > "$LOG_PATH/create-reused-empty-cluster-with-default-pgbouncer.yaml"
apiVersion: stackgres.io/v1
kind: SGCluster
metadata:
  name: $REUSED_CLUSTER_NAME
  namespace: $CLUSTER_NAMESPACE
spec:
  instances: 1
  postgres:
    version: "$E2E_POSTGRES_VERSION"
  configurations:
    observability:
      disableMetrics: true
  pods:
    persistentVolume:
      size: '5Gi'
    disableConnectionPooling: false
    disablePostgresUtil: true
    scheduling:
      nodeSelector:
        $NODE_LABEL_KEY: $NODE_LABEL_VALUE"
  nonProductionOptions:
    disableClusterPodAntiAffinity: true
EOF

  kubectl create -f "$LOG_PATH/create-reused-empty-cluster-with-default-pgbouncer.yaml"

  if kubectl get sgclusters -n "$CLUSTER_NAMESPACE" "$REUSED_CLUSTER_NAME"
  then
    echo "Cluster with defaul configuration already created. Succeed"
  else
    echo "Cluster with defaul configuration already created was not created"
    return 1
  fi

  kubectl delete sgcluster -n "$CLUSTER_NAMESPACE" "$REUSED_CLUSTER_NAME"
}

create_empty_cluster_with_no_sidecars() {
  cat << EOF > "$LOG_PATH/create-empty-cluster-with-no-sidecars.yaml"
apiVersion: stackgres.io/v1
kind: SGCluster
metadata:
  name: $NOSIDECARS_CLUSTER_NAME
  namespace: $CLUSTER_NAMESPACE
spec:
  instances: 1
  postgres:
    version: "$E2E_POSTGRES_VERSION"
  configurations:
    observability:
      disableMetrics: true
  pods:
    persistentVolume:
      size: '512Mi'
    disableConnectionPooling: true
    disablePostgresUtil: true
    scheduling:
      nodeSelector:
        $NODE_LABEL_KEY: $NODE_LABEL_VALUE"
  nonProductionOptions:
    disableClusterPodAntiAffinity: true
EOF

  kubectl create -f "$LOG_PATH/create-empty-cluster-with-no-sidecars.yaml"

  if kubectl get sgclusters -n "$CLUSTER_NAMESPACE" "$NOSIDECARS_CLUSTER_NAME"
  then
    echo "Cluster with no sidecars. Succeed"
  else
    echo "Cluster with no sidecars was not created."
    return 1
  fi

  local DISABLED_CONN_POOL
  DISABLED_CONN_POOL="$(kubectl get sgclusters.stackgres.io -n "$CLUSTER_NAMESPACE" "$NOSIDECARS_CLUSTER_NAME" -o json | jq -r '.spec.pods.disableConnectionPooling')"

  assert_string_equal "true" "$DISABLED_CONN_POOL"

  local DISABLED_METRIC_EXPORTER
  DISABLED_METRIC_EXPORTER="$(kubectl get sgclusters.stackgres.io -n "$CLUSTER_NAMESPACE" "$NOSIDECARS_CLUSTER_NAME" -o json | jq -r '.spec.configurations.observability.disableMetrics')"

  assert_string_equal "true" "$DISABLED_METRIC_EXPORTER"

  local DISABLED_POSTGRES_UTIL
  DISABLED_POSTGRES_UTIL="$(kubectl get sgclusters.stackgres.io -n "$CLUSTER_NAMESPACE" "$NOSIDECARS_CLUSTER_NAME" -o json | jq -r '.spec.pods.disablePostgresUtil')"

  assert_string_equal "true" "$DISABLED_POSTGRES_UTIL"

  kubectl delete sgcluster -n "$CLUSTER_NAMESPACE" "$NOSIDECARS_CLUSTER_NAME"
}

create_empty_cluster() {
  cat << EOF > "$LOG_PATH/create-empty-cluster.yaml"
apiVersion: stackgres.io/v1
kind: SGCluster
metadata:
  name: $CLUSTER_NAME
  namespace: $CLUSTER_NAMESPACE
spec:
  instances: 1
  postgres:
    version: "$E2E_POSTGRES_VERSION"
  pods:
    persistentVolume:
      size: '512Mi'
    scheduling:
      nodeSelector:
        $NODE_LABEL_KEY: $NODE_LABEL_VALUE"
  nonProductionOptions:
    disableClusterPodAntiAffinity: true
EOF

  kubectl create -f "$LOG_PATH/create-empty-cluster.yaml"

  local CREATED_PGCONFIG
  CREATED_PGCONFIG="$(kubectl get sgclusters.stackgres.io -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME" -o='jsonpath={.spec.configurations.sgPostgresConfig}')"

  if wait_until kubectl get sgpgconfigs.stackgres.io -n "$CLUSTER_NAMESPACE" "$CREATED_PGCONFIG"
  then
    success "Default pgconfig was created in the cluster namespace"
  else
    fail "Default pgconfig was not created in the cluster namespace"
  fi

  local CREATED_PGCONFIG_FIELDS
  CREATED_PGCONFIG_FIELDS="$(kubectl get sgpgconfigs.stackgres.io -n "$CLUSTER_NAMESPACE" "$CREATED_PGCONFIG" -o json | jq '.spec["postgresql.conf"] | length')"

  if [ "$CREATED_PGCONFIG_FIELDS" -gt 0 ]
  then
    success "Defaults pgconfig fields were created"
  else
    fail "Default pgconfig fields not created"
  fi

  local CREATED_PGBOUNCER
  CREATED_PGBOUNCER="$(kubectl get sgclusters.stackgres.io -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME" -o='jsonpath={.spec.configurations.sgPoolingConfig}')"

  if wait_until kubectl get sgpoolconfigs.stackgres.io -n "$CLUSTER_NAMESPACE" "$CREATED_PGBOUNCER"
  then
    success "Default poolconfig was created in the cluster namespace"
  else
    fail "Default poolconfig was not created in the cluster namespace"
  fi

  local CREATED_PGBOUNCER_FIELDS
  CREATED_PGBOUNCER_FIELDS="$(kubectl get sgpoolconfigs.stackgres.io -n "$CLUSTER_NAMESPACE" "$CREATED_PGBOUNCER" -o json | jq '.spec.pgBouncer["pgbouncer.ini"].pgbouncer | length')"

  if [ "$CREATED_PGBOUNCER_FIELDS" -gt 0 ]
  then
    success "Defaults poolconfig fields were created"
  else
    fail "Default poolconfig fields not created"
  fi

  local CREATED_PROFILE
  CREATED_PROFILE="$(kubectl get sgclusters.stackgres.io -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME" -o='jsonpath={.spec.sgInstanceProfile}')"

  if wait_until kubectl get sginstanceprofiles.stackgres.io -n "$CLUSTER_NAMESPACE" "$CREATED_PROFILE"
  then
    success "Default profile was created in the cluster namespace"
  else
    fail "Default profile was not created in the cluster namespace"
  fi

  local CREATED_PROFILE_FIELDS
  CREATED_PROFILE_FIELDS="$(kubectl get sginstanceprofiles.stackgres.io -n "$CLUSTER_NAMESPACE" "$CREATED_PROFILE" -o json | jq '.spec | length')"
  
  if [ -z "$CREATED_PROFILE_FIELDS" || "$CREATED_PROFILE_FIELDS" = "null" ]
  then
    fail "Default profile fields were not created"
  else
    success "Defaults profile fields were created"
  fi

  local DEFAULT_ANNOTATION
  DEFAULT_ANNOTATION="$(kubectl get sgclusters.stackgres.io -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME" -o json | jq '.metadata.annotations["stackgres.io/operatorVersion"]')"

  if [ -z "$DEFAULT_ANNOTATION" ] || [ "$DEFAULT_ANNOTATION" = "null" ]
  then
    fail "Default annotations not created"
  else
    success "Defaults annotations created"
  fi

  local INSTALLED_CONTAINERS
  INSTALLED_CONTAINERS="$(wait_until kubectl get sts -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME" -o=jsonpath='{.spec.template.spec.containers[*].name}')"

  assert_string_contains "prometheus-postgres-exporter" "$INSTALLED_CONTAINERS"
  if ! kubectl get sgcluster -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME" --template '{{ .spec.pods.disableEnvoy }}' | grep -qxF true
  then
    assert_string_contains "envoy" "$INSTALLED_CONTAINERS"
  fi
  assert_string_contains "pgbouncer" "$INSTALLED_CONTAINERS"
  assert_string_contains "postgres-util" "$INSTALLED_CONTAINERS"

  kubectl delete sgcluster -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME"
}

update_empty_cluster() {
  cat << EOF > "$LOG_PATH/update-empty-cluster.yaml"
apiVersion: stackgres.io/v1
kind: SGCluster
metadata:
  name: $CLUSTER_NAME
  namespace: $CLUSTER_NAMESPACE
spec:
  instances: 1
  postgres:
    version: "$E2E_POSTGRES_VERSION"
  pods:
    persistentVolume:
      size: '512Mi'
    scheduling:
      nodeSelector:
        $NODE_LABEL_KEY: $NODE_LABEL_VALUE"
  nonProductionOptions:
    disableClusterPodAntiAffinity: true
EOF

  kubectl create -f "$LOG_PATH/update-empty-cluster.yaml"

  kubectl get sgcluster -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME" -o json \
    | jq 'del(.metadata.resourceVersion)|del(.metadata.uid)|del(.metadata.creationTimestamp)|del(.metadata.selfLink)|del(.metadata.generation)' \
    | jq 'del(.metadata.annotations["stackgres.io/operatorVersion"])' \
    | kubectl create -f - --dry-run=client -o yaml > "$LOG_PATH/patch-empty-cluster.yaml"
  kubectl patch sgcluster -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME" --type merge --patch-file="$LOG_PATH/patch-empty-cluster.yaml"

  local DEFAULT_ANNOTATION
  DEFAULT_ANNOTATION="$(kubectl get sgclusters.stackgres.io -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME" -o json | jq '.metadata.annotations["stackgres.io/operatorVersion"]')"

  if [ -z "$DEFAULT_ANNOTATION" ] || [ "$DEFAULT_ANNOTATION" = "null" ]
  then
    fail "Default annotations not created"
  else
    success "Defaults annotations created"
  fi

  local INSTALLED_CONTAINERS
  INSTALLED_CONTAINERS="$(wait_until kubectl get sts -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME" -o=jsonpath='{.spec.template.spec.containers[*].name}')"

  assert_string_contains "prometheus-postgres-exporter" "$INSTALLED_CONTAINERS"
  if ! kubectl get sgcluster -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME" --template '{{ .spec.pods.disableEnvoy }}' | grep -qxF true
  then
    assert_string_contains "envoy" "$INSTALLED_CONTAINERS"
  fi
  assert_string_contains "pgbouncer" "$INSTALLED_CONTAINERS"
  assert_string_contains "postgres-util" "$INSTALLED_CONTAINERS"

  kubectl delete sgcluster -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME"
}

create_cluster_with_previous_postgres_version() {
  cat << EOF > "$LOG_PATH/create-cluster-with-previous-postgres-version.yaml"
apiVersion: stackgres.io/v1
kind: SGCluster
metadata:
  name: $CLUSTER_NAME
  namespace: $CLUSTER_NAMESPACE
spec:
  instances: 1
  postgres:
    version: '13'
  configurations:
    observability:
      disableMetrics: true
  pods:
    persistentVolume:
      size: '128Mi'
    disableConnectionPooling: true
    disablePostgresUtil: true
    scheduling:
      nodeSelector:
        $NODE_LABEL_KEY: $NODE_LABEL_VALUE"
  nonProductionOptions:
    disableClusterPodAntiAffinity: true
EOF

  kubectl create -f "$LOG_PATH/create-cluster-with-previous-postgres-version.yaml"

  if kubectl get sgclusters.stackgres.io -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME"
  then
    success "cluster was created with previous postgres version"
  else
    fail "cluster was not created with previous postgres version"
  fi

  kubectl delete sgcluster -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME"
}

create_empty_distributedlogs() {
  cat << EOF > "$LOG_PATH/create-empty-distributedlogs.yaml"
apiVersion: stackgres.io/v1
kind: SGDistributedLogs
metadata:
  name: $DISTRIBUTEDLOGS_NAME
  namespace: $CLUSTER_NAMESPACE
spec:
  persistentVolume:
    size: 128Mi
  scheduling:
    nodeSelector:
      $NODE_LABEL_KEY: $NODE_LABEL_VALUE"
  nonProductionOptions:
    disableClusterPodAntiAffinity: true
EOF

  kubectl create -f "$LOG_PATH/create-empty-distributedlogs.yaml"

  local CREATED_PGCONFIG
  CREATED_PGCONFIG="$(kubectl get sgdistributedlogs.stackgres.io -n "$CLUSTER_NAMESPACE" "$DISTRIBUTEDLOGS_NAME" -o='jsonpath={.spec.configurations.sgPostgresConfig}')"

  if wait_until kubectl get sgpgconfigs.stackgres.io -n "$CLUSTER_NAMESPACE" "$CREATED_PGCONFIG"
  then
    success "Default pgconfig was created in the cluster namespace"
  else
    fail "Default pgconfig was not created in the cluster namespace"
  fi

  local CREATED_PGCONFIG_FIELDS
  CREATED_PGCONFIG_FIELDS="$(kubectl get sgpgconfigs.stackgres.io -n "$CLUSTER_NAMESPACE" "$CREATED_PGCONFIG" -o json | jq '.spec["postgresql.conf"] | length')"

  if [ "$CREATED_PGCONFIG_FIELDS" -gt 0 ]
  then
    success "Defaults pgconfig fields were created"
  else
    fail "Default pgconfig fields not created"
  fi

  local CREATED_PROFILE
  CREATED_PROFILE="$(kubectl get sgdistributedlogs.stackgres.io -n "$CLUSTER_NAMESPACE" "$DISTRIBUTEDLOGS_NAME" -o='jsonpath={.spec.sgInstanceProfile}')"

  if wait_until kubectl get sginstanceprofiles.stackgres.io -n "$CLUSTER_NAMESPACE" "$CREATED_PROFILE"
  then
    success "Default profile was created in the distributed logs namespace"
  else
    fail "Default profile was not created in the distributed logs namespace"
  fi

  local CREATED_PROFILE_FIELDS
  CREATED_PROFILE_FIELDS="$(kubectl get sginstanceprofiles.stackgres.io -n "$CLUSTER_NAMESPACE" "$CREATED_PROFILE" -o json | jq '.spec | length')"
  
  if [ -z "$CREATED_PROFILE_FIELDS" || "$CREATED_PROFILE_FIELDS" = "null" ]
  then
    fail "Default profile fields were not created"
  else
    success "Defaults profile fields were created"
  fi

  local DEFAULT_ANNOTATION
  DEFAULT_ANNOTATION="$(kubectl get sgdistributedlogs.stackgres.io -n "$CLUSTER_NAMESPACE" "$DISTRIBUTEDLOGS_NAME" -o json | jq '.metadata.annotations["stackgres.io/operatorVersion"]')"

  if [ -z "$DEFAULT_ANNOTATION" ] || [ "$DEFAULT_ANNOTATION" = "null" ]
  then
    fail "Default annotations not created"
  else
    success "Defaults annotations created"
  fi
}

update_empty_distributedlogs() {
  kubectl get sgdistributedlogs -n "$CLUSTER_NAMESPACE" "$DISTRIBUTEDLOGS_NAME" -o json \
    | jq 'del(.metadata.resourceVersion)|del(.metadata.uid)|del(.metadata.creationTimestamp)|del(.metadata.selfLink)|del(.metadata.geneartion)' \
    | jq 'del(.metadata.annotations["stackgres.io/operatorVersion"])' \
    | kubectl create -f - --dry-run=client -o yaml > "$LOG_PATH/patch-empty_distributedlogs.yaml"
  kubectl patch sgdistributedlogs -n "$CLUSTER_NAMESPACE" "$DISTRIBUTEDLOGS_NAME" --type merge --patch-file="$LOG_PATH/patch-empty_distributedlogs.yaml"

  local DEFAULT_ANNOTATION
  DEFAULT_ANNOTATION="$(kubectl get sgdistributedlogs.stackgres.io -n "$CLUSTER_NAMESPACE" "$DISTRIBUTEDLOGS_NAME" -o json | jq '.metadata.annotations["stackgres.io/operatorVersion"]')"

  if [ -z "$DEFAULT_ANNOTATION" ] || [ "$DEFAULT_ANNOTATION" = "null" ]
  then
    fail "Default annotations not created"
  else
    success "Defaults annotations created"
  fi

  kubectl delete sgdistributedlogs -n "$CLUSTER_NAMESPACE" "$DISTRIBUTEDLOGS_NAME"
}

create_empty_sharded_cluster() {
  cat << EOF > "$LOG_PATH/create-empty-sharded-cluster.yaml"
apiVersion: stackgres.io/v1alpha1
kind: SGShardedCluster
metadata:
  name: $CLUSTER_NAME
  namespace: $CLUSTER_NAMESPACE
spec:
  type: citus
  database: citus
  postgres:
    version: "${E2E_CITUS_POSTGRES_VERSION:-$E2E_POSTGRES_VERSION}"
  coordinator:
    instances: 1
    pods:
      persistentVolume:
        size: '512Mi'
      scheduling:
        nodeSelector:
          $NODE_LABEL_KEY: $NODE_LABEL_VALUE"
  shards:
    clusters: 1
    instancesPerCluster: 1
    pods:
      persistentVolume:
        size: '512Mi'
      scheduling:
        nodeSelector:
          $NODE_LABEL_KEY: $NODE_LABEL_VALUE"
  nonProductionOptions:
    disableClusterPodAntiAffinity: true
EOF

  kubectl create -f "$LOG_PATH/create-empty-sharded-cluster.yaml"
  local CREATED_PGCONFIG
  CREATED_PGCONFIG="$(kubectl get sgshardedclusters.stackgres.io -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME" -o='jsonpath={.spec.coordinator.configurations.sgPostgresConfig}')"

  if wait_until kubectl get sgpgconfigs.stackgres.io -n "$CLUSTER_NAMESPACE" "$CREATED_PGCONFIG"
  then
    success "Default pgconfig was created in the cluster namespace"
  else
    fail "Default pgconfig was not created in the cluster namespace"
  fi

  local CREATED_PGCONFIG_FIELDS
  CREATED_PGCONFIG_FIELDS="$(kubectl get sgpgconfigs.stackgres.io -n "$CLUSTER_NAMESPACE" "$CREATED_PGCONFIG" -o json | jq '.spec["postgresql.conf"] | length')"

  if [ "$CREATED_PGCONFIG_FIELDS" -gt 0 ]
  then
    success "Defaults pgconfig fields were created"
  else
    fail "Default pgconfig fields not created"
  fi

  local CREATED_PGBOUNCER
  CREATED_PGBOUNCER="$(kubectl get sgshardedclusters.stackgres.io -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME" -o='jsonpath={.spec.coordinator.configurations.sgPoolingConfig}')"

  if wait_until kubectl get sgpoolconfigs.stackgres.io -n "$CLUSTER_NAMESPACE" "$CREATED_PGBOUNCER"
  then
    success "Default poolconfig was created in the cluster namespace"
  else
    fail "Default poolconfig was not created in the cluster namespace"
  fi

  local CREATED_PGBOUNCER_FIELDS
  CREATED_PGBOUNCER_FIELDS="$(kubectl get sgpoolconfigs.stackgres.io -n "$CLUSTER_NAMESPACE" "$CREATED_PGBOUNCER" -o json | jq '.spec.pgBouncer["pgbouncer.ini"].pgbouncer | length')"

  if [ "$CREATED_PGBOUNCER_FIELDS" -gt 0 ]
  then
    success "Defaults poolconfig fields were created"
  else
    fail "Default poolconfig fields not created"
  fi

  local CREATED_PROFILE
  CREATED_PROFILE="$(kubectl get sgshardedclusters.stackgres.io -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME" -o='jsonpath={.spec.coordinator.sgInstanceProfile}')"

  if wait_until kubectl get sginstanceprofiles.stackgres.io -n "$CLUSTER_NAMESPACE" "$CREATED_PROFILE"
  then
    success "Default profile was created in the cluster namespace"
  else
    fail "Default profile was not created in the cluster namespace"
  fi

  local CREATED_PROFILE_FIELDS
  CREATED_PROFILE_FIELDS="$(kubectl get sginstanceprofiles.stackgres.io -n "$CLUSTER_NAMESPACE" "$CREATED_PROFILE" -o json | jq '.spec | length')"
  
  if [ -z "$CREATED_PROFILE_FIELDS" || "$CREATED_PROFILE_FIELDS" = "null" ]
  then
    fail "Default profile fields were not created"
  else
    success "Defaults profile fields were created"
  fi

  local DEFAULT_ANNOTATION
  DEFAULT_ANNOTATION="$(kubectl get sgshardedclusters.stackgres.io -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME" -o json | jq '.metadata.annotations["stackgres.io/operatorVersion"]')"

  if [ -z "$DEFAULT_ANNOTATION" ] || [ "$DEFAULT_ANNOTATION" = "null" ]
  then
    fail "Default annotations not created"
  else
    success "Defaults annotations created"
  fi

  local INSTALLED_CONTAINERS
  INSTALLED_CONTAINERS="$(wait_until kubectl get sts -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME"-coord -o=jsonpath='{.spec.template.spec.containers[*].name}')"

  assert_string_contains "prometheus-postgres-exporter" "$INSTALLED_CONTAINERS"
  if ! kubectl get sgshardedcluster -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME" --template '{{ .spec.coordinator.pods.disableEnvoy }}' | grep -qxF true
  then
    assert_string_contains "envoy" "$INSTALLED_CONTAINERS"
  fi
  assert_string_contains "pgbouncer" "$INSTALLED_CONTAINERS"
  assert_string_contains "postgres-util" "$INSTALLED_CONTAINERS"

  INSTALLED_CONTAINERS="$(wait_until kubectl get sts -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME"-shard0 -o=jsonpath='{.spec.template.spec.containers[*].name}')"

  assert_string_contains "prometheus-postgres-exporter" "$INSTALLED_CONTAINERS"
  if ! kubectl get sgshardedcluster -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME" --template '{{ .spec.shards.pods.disableEnvoy }}' | grep -qxF true
  then
    assert_string_contains "envoy" "$INSTALLED_CONTAINERS"
  fi
  assert_string_contains "pgbouncer" "$INSTALLED_CONTAINERS"
  assert_string_contains "postgres-util" "$INSTALLED_CONTAINERS"

  kubectl delete sgshardedcluster -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME"
}

update_empty_sharded_cluster() {
  cat << EOF > "$LOG_PATH/update-empty-sharded-cluster.yaml"
apiVersion: stackgres.io/v1alpha1
kind: SGShardedCluster
metadata:
  name: $CLUSTER_NAME
  namespace: $CLUSTER_NAMESPACE
spec:
  type: citus
  database: citus
  postgres:
    version: "${E2E_CITUS_POSTGRES_VERSION:-$E2E_POSTGRES_VERSION}"
  coordinator:
    instances: 1
    pods:
      persistentVolume:
        size: '512Mi'
      scheduling:
        nodeSelector:
          $NODE_LABEL_KEY: $NODE_LABEL_VALUE"
  shards:
    clusters: 1
    instancesPerCluster: 1
    pods:
      persistentVolume:
        size: '512Mi'
      scheduling:
        nodeSelector:
          $NODE_LABEL_KEY: $NODE_LABEL_VALUE"
  nonProductionOptions:
    disableClusterPodAntiAffinity: true
EOF

  kubectl create -f "$LOG_PATH/update-empty-sharded-cluster.yaml"

  kubectl get sgshardedcluster -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME" -o json \
    | jq 'del(.metadata.resourceVersion)|del(.metadata.uid)|del(.metadata.creationTimestamp)|del(.metadata.selfLink)|del(.metadata.generation)' \
    | jq 'del(.metadata.annotations["stackgres.io/operatorVersion"])' \
    | kubectl create -f - --dry-run=client -o yaml > "$LOG_PATH/patch-empty-sharded-cluster.yaml"
  kubectl patch sgshardedcluster -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME" --type merge --patch-file="$LOG_PATH/patch-empty-sharded-cluster.yaml"

  local DEFAULT_ANNOTATION
  DEFAULT_ANNOTATION="$(kubectl get sgshardedclusters.stackgres.io -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME" -o json | jq '.metadata.annotations["stackgres.io/operatorVersion"]')"

  if [ -z "$DEFAULT_ANNOTATION" ] || [ "$DEFAULT_ANNOTATION" = "null" ]
  then
    fail "Default annotations not created"
  else
    success "Defaults annotations created"
  fi

  local INSTALLED_CONTAINERS
  INSTALLED_CONTAINERS="$(wait_until kubectl get sts -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME"-coord -o=jsonpath='{.spec.template.spec.containers[*].name}')"

  assert_string_contains "prometheus-postgres-exporter" "$INSTALLED_CONTAINERS"
  if ! kubectl get sgshardedcluster -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME" --template '{{ .spec.coordinator.pods.disableEnvoy }}' | grep -qxF true
  then
    assert_string_contains "envoy" "$INSTALLED_CONTAINERS"
  fi
  assert_string_contains "pgbouncer" "$INSTALLED_CONTAINERS"
  assert_string_contains "postgres-util" "$INSTALLED_CONTAINERS"

  INSTALLED_CONTAINERS="$(wait_until kubectl get sts -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME"-shard0 -o=jsonpath='{.spec.template.spec.containers[*].name}')"

  assert_string_contains "prometheus-postgres-exporter" "$INSTALLED_CONTAINERS"
  if ! kubectl get sgshardedcluster -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME" --template '{{ .spec.shards.pods.disableEnvoy }}' | grep -qxF true
  then
    assert_string_contains "envoy" "$INSTALLED_CONTAINERS"
  fi
  assert_string_contains "pgbouncer" "$INSTALLED_CONTAINERS"
  assert_string_contains "postgres-util" "$INSTALLED_CONTAINERS"

  kubectl delete sgshardedcluster -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME"
}

create_sharded_cluster_with_previous_postgres_version() {
  cat << EOF > "$LOG_PATH/create-sharded-cluster-with-previous-postgres-version.yaml"
apiVersion: stackgres.io/v1alpha1
kind: SGShardedCluster
metadata:
  name: $CLUSTER_NAME
  namespace: $CLUSTER_NAMESPACE
spec:
  type: citus
  database: citus
  postgres:
    version: '13'
  configurations:
    observability:
      disableMetrics: true
  coordinator:
    instances: 1
    pods:
      persistentVolume:
        size: '128Mi'
      disableConnectionPooling: true
      disablePostgresUtil: true
      scheduling:
        nodeSelector:
          $NODE_LABEL_KEY: $NODE_LABEL_VALUE"
  shards:
    clusters: 1
    instancesPerCluster: 1
    pods:
      persistentVolume:
        size: '128Mi'
      disableConnectionPooling: true
      disablePostgresUtil: true
      scheduling:
        nodeSelector:
          $NODE_LABEL_KEY: $NODE_LABEL_VALUE"
  nonProductionOptions:
    disableClusterPodAntiAffinity: true
EOF

  kubectl create -f "$LOG_PATH/create-sharded-cluster-with-previous-postgres-version.yaml"

  if kubectl get sgshardedclusters.stackgres.io -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME"
  then
    success "cluster was created with previous postgres version"
  else
    fail "cluster was not created with previous postgres version"
  fi

  kubectl delete sgshardedcluster -n "$CLUSTER_NAMESPACE" "$CLUSTER_NAME"
}
